package com.dinglian.ots.shiro;

import com.alibaba.fastjson.JSONObject;
import com.dinglian.ots.common.EncryptHelper;
import com.dinglian.ots.common.model.Constant;
import com.dinglian.ots.exception.GlobalException;
import com.dinglian.ots.redis.*;
import com.dinglian.ots.result.CodeMsg;
import com.dinglian.ots.service.UserService;
import com.dinglian.ots.vo.user.UserVo;
import org.apache.commons.lang3.StringUtils;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.*;
import org.apache.shiro.authz.AuthorizationInfo;
import org.apache.shiro.authz.SimpleAuthorizationInfo;
import org.apache.shiro.mgt.SessionsSecurityManager;
import org.apache.shiro.realm.AuthorizingRealm;
import org.apache.shiro.session.Session;
import org.apache.shiro.session.mgt.DefaultSessionManager;
import org.apache.shiro.subject.PrincipalCollection;
import org.apache.shiro.subject.Subject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.kafka.KafkaProperties;

import java.util.Collection;
import java.util.LinkedHashSet;
import java.util.Set;


/**
 * 身份校验核心类;
 *
 * @author ZZ
 * @version v.0.1
 */
public class MyShiroRealm extends AuthorizingRealm {

    @Autowired
    private UserService userService;

    @Autowired
    RedisService redisService;


    //执行认证逻辑
    @Override
    protected AuthenticationInfo doGetAuthenticationInfo(AuthenticationToken authenticationToken) throws AuthenticationException {
        MyShiroToken token = (MyShiroToken) authenticationToken;
        String username = token.getUsername();
        Integer roleType = token.getRoleType();

        UserVo user = userService.getUserByUserName(username);
        if (user == null) {
            return null;
        }


        Session session = SecurityUtils.getSubject().getSession();
        String password = null;
        if (user.getRoleId() == Constant.BRAND_ROLE || user.getRoleId() == Constant.SHOWROOM_ROLE) {

            //测试账号
            if ("13166113899".equals(username) || "18622986582".equals(username)) {
                password = "angelchen2020";
                user.setPassword(password);
            } else {
                boolean isExist = redisService.exists(CodeKey.getKey, username);
                if (!isExist) {
                    throw new GlobalException(CodeMsg.CODE_ERROR);
                }
                //从redis中获取正确的验证码
                String rightCode = redisService.get(CodeKey.getKey, username, String.class);
                user.setPassword(token.getPassword().toString());
                password = rightCode;
            }

        } else {
                    password = user.getPassword();
//                    password = EncryptHelper.SHA1(password);
        }

        String sessionToken = EncryptHelper.SHA1(user.getUsername() + System.currentTimeMillis());
        user.setSessionToken(sessionToken);

        redisService.set(UserKey.getKey, sessionToken, user);
/*
        // username + password => token
        String authJson = redisService.get(TokenMapKey.getKey, EncryptHelper.SHA1(user.getUsername()), String.class);
        JSONObject authInfo = new JSONObject();
        if (StringUtils.isNotBlank(authJson)) {
            authInfo = JSONObject.parseObject(authJson);
            String originToken = authInfo.getString("sessionToken");
            if (StringUtils.isNotBlank(originToken) && !originToken.equals(sessionToken)) {
                // 判断为一次新的登陆，删除旧登陆映射
                redisService.delete(UserKey.getKey, originToken);
            }
            // 否则不做其他操作
        }

        // 重新登陆重新覆盖映射
        authInfo.put("sessionToken", sessionToken);
        authInfo.put("sessionId", sessionId);
        redisService.set(TokenMapKey.getKey, EncryptHelper.SHA1(user.getUsername()), authInfo.toJSONString());*/

        session.setAttribute(Constant.SESSION_USER, user);
        return new SimpleAuthenticationInfo(user, password, getName());
    }

    @Override
    protected AuthorizationInfo doGetAuthorizationInfo(PrincipalCollection principals) {
        SimpleAuthorizationInfo info = new SimpleAuthorizationInfo();
      /*  Subject subject = SecurityUtils.getSubject();
        UserVo userVo = (UserVo) subject.getSession().getAttribute(Constant.SESSION_USER);
        String roleName = userVo.getRoleName();
        Set<String> roles = new LinkedHashSet<>();
        roles.add(roleName);
        info.setRoles(roles);*/
        return info;
    }

}
